import json
import logging

import pandas as pd
from PySide6.QtWidgets import QWidget, QVBoxLayout, QHBoxLayout, QLabel, QDateEdit, QPushButton, QComboBox, \
    QTableWidget, QTableWidgetItem, QLineEdit, QHeaderView, QFileDialog
from PySide6.QtCore import Qt, QDate

from kumquat_king_pyside6.app_config import ORDER_HEADERS, ORDER_STATUS, ORDER_MAPPINGS, SHUNFENG_MAPPINGS, PERSONAL_INFO, \
    EXCEL_REPORT_HEADERS, ORDER_EXCEL_MAPPINGS, SHUNFENG_TPL_HEADERS
from kumquat_king_pyside6.controls.apis import get_orders_by_filter
from kumquat_king_pyside6.pages.order_report_page import OrderReportPage

from kumquat_king_pyside6.tools import kumquat_format_converter, message_box


class ViewOrderPage(QWidget):
    """
    这个页面用于展示和筛选订单，可以通过开始日期和结束日期从数据库获取订单数据，UI需要有一个日期筛选器以及确定按钮
    在拿到数据后，可以通过筛选线人，日期，金桔种类进行table层面的显示， UI需要有一个日期筛选器，金桔combox，和线人combox，以及搜索按钮
    数据将会显示在一个table里
    """

    def __init__(self, kumquatFormat, presenters):
        super().__init__()
        self.setObjectName("VIEW_ORDER_PAGE")
        self.kumquatFormat = kumquatFormat
        self.presenters = presenters
        self.init_args()
        self.init_ui()
        self.init_slots()

    def init_args(self):
        self.ordersDf = pd.DataFrame()
        self.orders = []
        self.reportPage = None

    def init_ui(self):
        layout = QVBoxLayout()

        # 日期筛选器
        dateLayout = QHBoxLayout()
        start_label = QLabel("开始日期:")
        self.startDateEdit = QDateEdit()
        end_label = QLabel("结束日期:")
        self.endDateEdit = QDateEdit()
        self.startDateEdit.setDate(QDate.currentDate())
        self.endDateEdit.setDate(QDate.currentDate().addDays(1))
        dateLayout.addWidget(start_label)
        dateLayout.addWidget(self.startDateEdit)
        dateLayout.addWidget(end_label)
        dateLayout.addWidget(self.endDateEdit)
        layout.addLayout(dateLayout)

        # 金桔种类组合框
        kumquat_layout = QHBoxLayout()
        kumquatLabel = QLabel("金桔种类:")
        self.kumquatCombo = QComboBox()
        kumquatFormatList = ['']
        kumquatFormatList.extend([kumquat_format_converter(x['name'] + ' ' + x['style'], 'ST2ZH')
                                  for x in self.kumquatFormat])
        self.kumquatCombo.addItems(kumquatFormatList)  # 假设的金桔种类
        kumquat_layout.addWidget(kumquatLabel)
        kumquat_layout.addWidget(self.kumquatCombo)
        layout.addLayout(kumquat_layout)

        # 线人组合框
        informantLayout = QHBoxLayout()
        informantLabel = QLabel("线人:")
        self.presenterCombo = QComboBox()
        presenterList = ['']
        presenterList.extend([x['presenter'] for x in self.presenters])
        self.presenterCombo.addItems(presenterList)
        informantLayout.addWidget(informantLabel)
        informantLayout.addWidget(self.presenterCombo)
        layout.addLayout(informantLayout)

        # status combo
        statusLayout = QHBoxLayout()
        statusLabel = QLabel("订单状态:")
        self.statusCombo = QComboBox()
        orderStatus = ['']
        orderStatus.extend(ORDER_STATUS)
        self.statusCombo.addItems(orderStatus)
        statusLayout.addWidget(statusLabel)
        statusLayout.addWidget(self.statusCombo)
        layout.addLayout(statusLayout)

        # note edit
        noteLayout = QHBoxLayout()
        noteLabel = QLabel("备注:")
        self.noteEdit = QLineEdit()
        noteLayout.addWidget(noteLabel)
        noteLayout.addWidget(self.noteEdit)
        layout.addLayout(noteLayout)

        # 搜索按钮
        self.filterBtn = QPushButton("搜索")
        layout.addWidget(self.filterBtn)

        # 表格
        self.table = QTableWidget()
        self.table.setColumnCount(len(ORDER_HEADERS))
        self.table.setHorizontalHeaderLabels(ORDER_HEADERS)
        self.table.setSortingEnabled(True)

        # 设置表格为可滚动
        self.table.setVerticalScrollBarPolicy(Qt.ScrollBarPolicy.ScrollBarAsNeeded)
        self.table.setHorizontalScrollBarPolicy(Qt.ScrollBarPolicy.ScrollBarAsNeeded)

        layout.addWidget(self.table)

        # 根据orders数据查看报表
        bottomBtnLayout = QHBoxLayout()
        self.reportBtn = QPushButton("生成报表")
        self.toExcelBtn = QPushButton("导出为Excel")
        self.toExcelBtn.setToolTip("Excel格式包括order信息，顺丰模板，以及汇总，方便装货")
        bottomBtnLayout.addWidget(self.reportBtn)
        bottomBtnLayout.addWidget(self.toExcelBtn)
        layout.addLayout(bottomBtnLayout)
        self.setLayout(layout)

    def init_slots(self):
        self.filterBtn.clicked.connect(self.pull_orders)
        self.reportBtn.clicked.connect(self.report_orders)
        self.toExcelBtn.clicked.connect(self.to_excel_file)

    def pull_orders(self):
        # 假设这里从数据库获取数据
        # ORDER_HEADERS = ['客户', '金桔', '数量', '折扣', '总价', '单件原价', '线人', '订购日期']
        if self.kumquatCombo.currentText() == '':
            kumquatName = ''
            kumquatStyle = ''
        else:
            kumquatName, kumquatStyle = kumquat_format_converter(self.kumquatCombo.currentText())
        filters = {
            'start_date': self.startDateEdit.date().toPython().strftime('%Y-%m-%d'),
            'end_date': self.endDateEdit.date().toPython().strftime('%Y-%m-%d'),
            'kumquat_name': kumquatName,
            'kumquat_style': kumquatStyle,
            'customer_presenter': self.presenterCombo.currentText(),
            'note': self.noteEdit.text(),
            'status': self.statusCombo.currentText(),
        }
        logging.info(f"Request orders with filters: {filters}")
        requestCode, data = get_orders_by_filter(json.dumps(filters, ensure_ascii=False))
        if requestCode is None or requestCode not in [200, 201]:
            logging.error("Failed to fetch the order data: " + data)
            message_box("错误", "获取订单失败")
        self.orders = data[0]['data']
        logging.info(f"Orders data length: {len(self.orders)}")
        self.ordersDf = pd.DataFrame(self.orders)
        self.table.clearContents()
        self.table.setRowCount(len(self.orders))
        for row, order in enumerate(self.orders):
            self.table.setItem(row, 0, QTableWidgetItem(order['customer__name']))
            self.table.setItem(row, 1, QTableWidgetItem(kumquat_format_converter(order['kumquat__name'] + ' '
                                                                                 + order['kumquat__style'], 'ST2ZH')))
            self.table.setItem(row, 2, QTableWidgetItem(str(order['quantity'])))
            self.table.setItem(row, 3, QTableWidgetItem(str(order['on_sold'])))
            self.table.setItem(row, 4, QTableWidgetItem(str(order['price'])))
            # self.table.setItem(row, 5, QTableWidgetItem(order['kumquat__original_price']))
            self.table.setItem(row, 5, QTableWidgetItem(order['customer__presenter']))
            self.table.setItem(row, 6, QTableWidgetItem(order['book_date']))
        self.table.resizeColumnsToContents()
        self.table.horizontalHeader().setSectionResizeMode(QHeaderView.Stretch)
        header = self.table.horizontalHeader()
        header.setSectionsMovable(True)

    def report_orders(self):
        if self.ordersDf.empty:
            message_box("错误", "当前没有数据，请先搜索订单")
            return
        if self.reportPage is None or not self.reportPage.isVisible():
            self.reportPage = OrderReportPage(self.ordersDf)
            self.reportPage.show()
        else:
            self.reportPage.raise_()

    def to_excel_file(self):
        excel_file_name = QFileDialog.getSaveFileName(self, "保存Excel文件", "./excels", "Excel Files (*.xlsx)")[0]
        if excel_file_name:
            try:
                ordersDF = self.ordersDf.rename(columns=ORDER_EXCEL_MAPPINGS)
                dfList = [ordersDF]
                dateStr = ordersDF['订购日期'].to_list()[0][0:11]
                dated_sheet_name = dateStr + '_orders'
                sheets_name = [dated_sheet_name]
                shunfeng_sheet_name = dateStr + '_顺丰模板'
                sheets_name.append(shunfeng_sheet_name)

                shunfeng_df = pd.DataFrame(columns=SHUNFENG_TPL_HEADERS)
                doubleList = []
                for col in SHUNFENG_MAPPINGS:
                    shunfeng_df[col] = ordersDF[SHUNFENG_MAPPINGS.get(col)]
                for ele in PERSONAL_INFO:
                    shunfeng_df[ele] = PERSONAL_INFO[ele]
                shunfeng_df['托寄物内容'] = ordersDF['订购金桔'] + ' ' + ordersDF['规格']
                for index, row in shunfeng_df.iterrows():
                    size = row['托寄物数量']
                    if size > 1:
                        doubleList.extend([row] * (int(size) - 1))

                shunfeng_double_df = pd.DataFrame(doubleList, columns=shunfeng_df.columns)
                shunfeng_df = pd.concat([shunfeng_df, shunfeng_double_df], ignore_index=True)
                shunfeng_df['托寄物数量'] = [1] * len(shunfeng_df)

                assert len(shunfeng_df) == ordersDF['数量'].sum(), \
                    logging.error(f"Export Excel with length issue: {len(shunfeng_df)} with {ordersDF['数量'].sum()}")
                dfList.append(shunfeng_df.sort_values(by=['收件人']))
                report_sheet_name = dateStr + '_金桔报表'
                report_df = self.build_report_df(ordersDF)
                dfList.append(report_df)
                sheets_name.append(report_sheet_name)
                save_file_name = excel_file_name  # + "\\" + dateStr + '_金桔订单.xlsx'
                with pd.ExcelWriter(save_file_name) as writer:
                    for dfEle, sheet_name in zip(dfList, sheets_name):
                        dfEle.to_excel(writer, sheet_name=sheet_name, index=False)
                        logging.info(f"Export orders to sheets name:{sheet_name}")
                logging.info(f"Export excel to : " + save_file_name)
                message_box("提示", f"导出成功到文件夹{save_file_name}")
            except Exception as e:
                logging.error(e)
                import pdb
                pdb.set_trace()
                message_box("错误", "导出失败")

    def build_report_df(self, df_to_report):
        """
        构建金桔报表 DataFrame。

        :param df_to_report: 用于构建报表的 DataFrame。
        :type df_to_report: pandas.DataFrame
        :return: 金桔报表 DataFrame。
        :rtype: pandas.DataFrame
        """
        report_df = pd.DataFrame(columns=EXCEL_REPORT_HEADERS)
        df_to_report['金桔类目'] = df_to_report['订购金桔'] + ' ' + df_to_report['规格']
        report_df[EXCEL_REPORT_HEADERS[0]] = df_to_report['金桔类目'].unique()
        size_list = []
        revenue_list = []
        for cls in report_df[EXCEL_REPORT_HEADERS[0]]:
            size = df_to_report[df_to_report['金桔类目'] == cls]['数量'].sum()
            revenue = df_to_report[(df_to_report['金桔类目'] == cls)]['price'].sum()
            size_list.append(size)
            revenue_list.append(revenue * size)
        report_df[EXCEL_REPORT_HEADERS[1]] = size_list
        report_df[EXCEL_REPORT_HEADERS[2]] = revenue_list
        report_df.loc[len(report_df)] = {EXCEL_REPORT_HEADERS[0]: '总计', EXCEL_REPORT_HEADERS[1]: sum(size_list),
                                         EXCEL_REPORT_HEADERS[2]: sum(revenue_list)}
        return report_df
